package com.fangcun.service.api.impl.v2;

import javax.transaction.Transactional;

import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import com.fangcun.bean.api.user.request.H5BindPhoneRequest;
import com.fangcun.bean.api.user.request.H5WechatLoginRequest;
import com.fangcun.bean.api.user.request.XcxLoginRequest;
import com.fangcun.bean.api.user.response.UserResponse;
import com.fangcun.common.auth.UserAuthMethod;
import com.fangcun.common.canstant.ErrCode;
import com.fangcun.common.canstant.PublicConstant;
import com.fangcun.common.exception.ProAffairException;
import com.fangcun.common.exception.ProRunTimeException;
import com.fangcun.common.util.BeanMapper;
import com.fangcun.common.util.PublicMethod;
import com.fangcun.common.util.json.JSONTools;
import com.fangcun.common.util.tencent.WechatAccessToken;
import com.fangcun.common.util.tencent.WechatUserInfo;
import com.fangcun.entity.User;
import com.fangcun.entity.UserLogin;
import com.fangcun.service.api.impl.ApiUserServiceImpl;

/**
 * @作者： 陳曉鬆 @时间： 2020年4月27日 - 上午9:27:42 @description：->
 */
@Service("apiUserServiceV2")
public class ApiUserServiceImplV2 extends ApiUserServiceImpl {

	@Override
	@Transactional
	public UserResponse h5WechatLogin(H5WechatLoginRequest request) throws ProAffairException {
		if (StringUtils.isEmpty(request.getAppid()) || StringUtils.isEmpty(request.getCode())) {
			throw new ProRunTimeException(ErrCode.ERR_PARAMETER.getReturnCode(), ErrCode.ERR_PARAMETER.getReturnMsg());
		}
		// 获取openid
		WechatAccessToken tencentLoginBean = tencentUtils.getH5OpenId(request.getAppid(), request.getCode());
		if (tencentLoginBean == null || StringUtils.isEmpty(tencentLoginBean.getOpenid())) {
			throw new ProRunTimeException(ErrCode.USER_GETWECHAT_FAIL.getReturnCode(), ErrCode.USER_GETWECHAT_FAIL.getReturnMsg());
		}
		User user = userMapper.selectByAppidAndOpenid(request.getAppid(), tencentLoginBean.getOpenid());
		boolean isLogin = false;
		if (user == null) {
			isLogin = true;
		} else if (StringUtils.isEmpty(user.getPhone())) {
			isLogin = true;
		}

		UserResponse response = new UserResponse();
		if (isLogin) {
			redisService.set(UserAuthMethod.LOGIN_REDIS_DB, UserAuthMethod.getBindPhoneRedisKey(request.getAppid(), tencentLoginBean.getOpenid()),
					JSONTools.obj2json(tencentLoginBean) + ">>>" + JSONTools.obj2json(request), 15 * 60);
		} else {
			setLoginToken(user);
			response = BeanMapper.map(user, UserResponse.class);
		}
		response.setOpenid(tencentLoginBean.getOpenid());
		return response;
	}

	@Override
	@Transactional
	public UserResponse h5BindPhone(H5BindPhoneRequest request) throws ProAffairException {
		String redisKey = request.getPhone() + "_" + PublicConstant.VERIFICATION_CODE_TYPE_6;
		Object objcode = redisService.get(UserAuthMethod.LOGIN_REDIS_DB, redisKey);
		if (StringUtils.isEmpty(objcode)) {
			throw new ProRunTimeException(ErrCode.VERIFICATIONCODE_BE_OVERDUE.getReturnCode(), ErrCode.VERIFICATIONCODE_BE_OVERDUE.getReturnMsg());
		}
		if (!objcode.toString().equals(request.getCode())) {
			throw new ProRunTimeException(ErrCode.VERIFICATIONCODE_FAIL.getReturnCode(), ErrCode.VERIFICATIONCODE_FAIL.getReturnMsg());
		}
		Object obj = redisService.get(UserAuthMethod.LOGIN_REDIS_DB, UserAuthMethod.getBindPhoneRedisKey(request.getAppid(), request.getOpenid()));
		if (StringUtils.isEmpty(obj)) {
			throw new ProRunTimeException(ErrCode.USER_LOGIN_BE_OVERDUE.getReturnCode(), ErrCode.USER_LOGIN_BE_OVERDUE.getReturnMsg() + ".");
		}
		String str[] = obj.toString().split(">>>");
		WechatAccessToken tencentLoginBean = JSONTools.jsonStr2obj(str[0], WechatAccessToken.class);
		if (tencentLoginBean == null) {
			throw new ProRunTimeException(ErrCode.USER_LOGIN_BE_OVERDUE.getReturnCode(), ErrCode.USER_LOGIN_BE_OVERDUE.getReturnMsg() + "..");
		}
		User user = userMapper.selectByAppidAndOpenid(request.getAppid(), request.getOpenid());
		if (user == null) {
			user = userMapper.selectByPhone(request.getPhone());
			if (user == null) {
				XcxLoginRequest requestParam = JSONTools.jsonStr2obj(str[0], XcxLoginRequest.class);
				user = new User();
				user.setUserName("用户_" + tencentLoginBean.getOpenid().substring(tencentLoginBean.getOpenid().length() - 6));
				// 绑定手机号
				user.setPhone(request.getPhone());
				if (requestParam.getRecommendUserId() != null && PublicMethod.isNumber(requestParam.getRecommendUserId().toString())) {
					user.setRecommendUserId(requestParam.getRecommendUserId());
				}
				if (!StringUtils.isEmpty(tencentLoginBean.getUnionid())) {
					user.setUnionid(tencentLoginBean.getUnionid());
				}
				int result = userMapper.insertSelective(user);
				if (result == 0 || user.getId() == null) {
					throw new ProRunTimeException(ErrCode.USER_DB_INSERT_FAIL.getReturnCode(), ErrCode.USER_DB_INSERT_FAIL.getReturnMsg());
				}
			} else {
				// 绑定手机号
				user.setPhone(request.getPhone());
			}
		} else {
			// 绑定手机号
			user.setPhone(request.getPhone());
		}
		UserLogin userLogin = userLoginMapper.selectByUserIdAndAppid(user.getId(), request.getAppid());
		if (userLogin == null) {
			UserLogin login = new UserLogin();
			login.setUserId(user.getId());
			login.setAppid(request.getAppid());
			login.setOpenid(tencentLoginBean.getOpenid());
			if (userLoginMapper.insertSelective(login) == 0) {
				throw new ProRunTimeException(ErrCode.USER_DB_INSERT_FAIL.getReturnCode(), ErrCode.USER_DB_INSERT_FAIL.getReturnMsg());
			}
		}

		user = userMapper.selectByAppidAndOpenid(request.getAppid(), tencentLoginBean.getOpenid());
		if (user == null) {
			throw new ProRunTimeException(ErrCode.USER_LOGIN_BE_OVERDUE.getReturnCode(), ErrCode.USER_LOGIN_BE_OVERDUE.getReturnMsg());
		}

		if (StringUtils.isEmpty(user.getHeadImageUrl())) {
			WechatUserInfo userInfo = tencentUtils.getWechatUserInfo(tencentLoginBean.getAccess_token(), tencentLoginBean.getOpenid());
			if (userInfo != null) {
				user.setUserName(userInfo.getNickname());
				user.setHeadImageUrl(userInfo.getHeadimgurl());
				userMapper.updateByPrimaryKeySelective(user);
			}
		}

		redisService.remove(UserAuthMethod.LOGIN_REDIS_DB, UserAuthMethod.getBindPhoneRedisKey(request.getAppid(), request.getOpenid()));

		setLoginToken(user);
		return BeanMapper.map(user, UserResponse.class);
	}

	public static void main(String[] args) {
		BeanMapper.map(new User(), UserResponse.class);
	}
}
